const { body, param, query, validationResult } = require('express-validator');

// 处理验证错误的中间件
const handleValidationErrors = (req, res, next) => {
  const errors = validationResult(req);
  if (!errors.isEmpty()) {
    return res.status(400).json({
      success: false,
      message: '输入数据验证失败',
      errors: errors.array().map(error => ({
        field: error.path,
        message: error.msg,
        value: error.value
      }))
    });
  }
  next();
};

// 用户注册验证
const validateUserRegistration = [
  body('username')
    .isLength({ min: 3, max: 50 })
    .withMessage('用户名长度必须在3-50个字符之间')
    .matches(/^[a-zA-Z0-9_]+$/)
    .withMessage('用户名只能包含字母、数字和下划线'),
  
  body('password')
    .isLength({ min: 6, max: 100 })
    .withMessage('密码长度必须在6-100个字符之间'),
  
  body('email')
    .optional()
    .isEmail()
    .withMessage('请输入有效的邮箱地址'),
  
  body('nickname')
    .optional()
    .isLength({ max: 50 })
    .withMessage('昵称长度不能超过50个字符'),
  
  body('phone')
    .optional()
    .matches(/^1[3-9]\d{9}$/)
    .withMessage('请输入有效的手机号码'),
  
  handleValidationErrors
];

// 用户登录验证
const validateUserLogin = [
  body('username')
    .notEmpty()
    .withMessage('用户名不能为空'),
  
  body('password')
    .notEmpty()
    .withMessage('密码不能为空'),
  
  handleValidationErrors
];

// 创建预约验证
const validateAppointmentCreation = [
  body('title')
    .isLength({ min: 1, max: 100 })
    .withMessage('预约标题长度必须在1-100个字符之间'),
  
  body('game_name')
    .isLength({ min: 1, max: 100 })
    .withMessage('游戏名称长度必须在1-100个字符之间'),
  
  body('category_id')
    .optional()
    .isInt({ min: 1 })
    .withMessage('游戏类型ID必须是正整数'),
  
  body('description')
    .optional()
    .isLength({ max: 1000 })
    .withMessage('描述长度不能超过1000个字符'),
  
  body('max_players')
    .isInt({ min: 2, max: 100 })
    .withMessage('最大人数必须在2-100之间'),
  
  body('scheduled_time')
    .isISO8601()
    .withMessage('请输入有效的时间格式')
    .custom((value) => {
      const scheduledTime = new Date(value);
      const now = new Date();
      if (scheduledTime <= now) {
        throw new Error('预约时间必须是未来时间');
      }
      return true;
    }),
  
  body('requirements')
    .optional()
    .isLength({ max: 500 })
    .withMessage('参与要求长度不能超过500个字符'),
  
  body('contact_info')
    .optional()
    .isLength({ max: 255 })
    .withMessage('联系方式长度不能超过255个字符'),
  
  body('is_public')
    .optional()
    .isBoolean()
    .withMessage('是否公开必须是布尔值'),
  
  handleValidationErrors
];

// 更新预约验证
const validateAppointmentUpdate = [
  body('title')
    .optional()
    .isLength({ min: 1, max: 100 })
    .withMessage('预约标题长度必须在1-100个字符之间'),
  
  body('game_name')
    .optional()
    .isLength({ min: 1, max: 100 })
    .withMessage('游戏名称长度必须在1-100个字符之间'),
  
  body('category_id')
    .optional()
    .isInt({ min: 1 })
    .withMessage('游戏类型ID必须是正整数'),
  
  body('description')
    .optional()
    .isLength({ max: 1000 })
    .withMessage('描述长度不能超过1000个字符'),
  
  body('max_players')
    .optional()
    .isInt({ min: 2, max: 100 })
    .withMessage('最大人数必须在2-100之间'),
  
  body('scheduled_time')
    .optional()
    .isISO8601()
    .withMessage('请输入有效的时间格式'),
  
  body('requirements')
    .optional()
    .isLength({ max: 500 })
    .withMessage('参与要求长度不能超过500个字符'),
  
  body('contact_info')
    .optional()
    .isLength({ max: 255 })
    .withMessage('联系方式长度不能超过255个字符'),
  
  body('is_public')
    .optional()
    .isBoolean()
    .withMessage('是否公开必须是布尔值'),
  
  body('status')
    .optional()
    .isIn(['active', 'full', 'cancelled', 'completed'])
    .withMessage('状态值无效'),
  
  handleValidationErrors
];

// 创建申请验证
const validateApplicationCreation = [
  body('appointment_id')
    .isInt({ min: 1 })
    .withMessage('预约ID必须是正整数'),
  
  body('reason')
    .isLength({ min: 1, max: 500 })
    .withMessage('申请原因长度必须在1-500个字符之间'),
  
  handleValidationErrors
];

// 处理申请验证
const validateApplicationProcess = [
  body('status')
    .isIn(['approved', 'rejected'])
    .withMessage('状态必须是approved或rejected'),
  
  body('admin_notes')
    .optional()
    .isLength({ max: 500 })
    .withMessage('管理员备注长度不能超过500个字符'),
  
  handleValidationErrors
];

// ID参数验证
const validateId = [
  param('id')
    .isInt({ min: 1 })
    .withMessage('ID必须是正整数'),
  
  handleValidationErrors
];

// 分页参数验证
const validatePagination = [
  query('page')
    .optional()
    .isInt({ min: 1 })
    .withMessage('页码必须是正整数'),
  
  query('limit')
    .optional()
    .isInt({ min: 1, max: 100 })
    .withMessage('每页数量必须在1-100之间'),
  
  handleValidationErrors
];

// 搜索参数验证
const validateSearch = [
  query('keyword')
    .optional()
    .isLength({ max: 100 })
    .withMessage('搜索关键词长度不能超过100个字符'),

  query('category_id')
    .optional()
    .custom((value) => {
      // 允许数字ID或游戏类型名称
      if (value && !(/^\d+$/.test(value) || ['MOBA', 'FPS', 'RPG', 'RTS', 'MMO', '其他'].includes(value))) {
        throw new Error('游戏类型必须是有效的ID或类型名称');
      }
      return true;
    }),

  query('status')
    .optional()
    .isIn(['active', 'full', 'cancelled', 'completed'])
    .withMessage('状态值无效'),

  handleValidationErrors
];

module.exports = {
  handleValidationErrors,
  validateUserRegistration,
  validateUserLogin,
  validateAppointmentCreation,
  validateAppointmentUpdate,
  validateApplicationCreation,
  validateApplicationProcess,
  validateId,
  validatePagination,
  validateSearch
};
